extends Node2D

# 蛇的参数
@onready var line: Line2D = $Line2D
@onready var timer: Timer = $Timer
var x_increment: float = 15.0
var max_line_length: float = 800.0
var move_speed: float = 12.0
var smooth_factor: float = 0.3
var timer_interval: float = 0.02
var start_point: Vector2
var current_direction: float = 0.0

# 光圈系统
var pulse_radius: float = 0.0
var max_pulse_radius: float = 400.0
var pulse_speed: float = 500.0
var is_pulsing: bool = false
var detected_edges: Array = []  # 存储检测到的边缘点 {points, lifetime}
var edge_lifetime: float = 3.0  # 边缘显示时间
var edge_color: Color = Color.WHITE

func _ready():
	timer.wait_time = timer_interval
	var screen_size = get_viewport_rect().size
	start_point = Vector2(-50, screen_size.y / 2)
	
	initialize_line()
	timer.timeout.connect(_on_timer_timeout)

func initialize_line():
	line.clear_points()
	var initial_points = 15
	for i in range(initial_points):
		var x_offset = i * 20.0
		var point = start_point + Vector2(x_offset, 0)
		line.add_point(point)

func _on_timer_timeout():
	var mouse_pos = get_global_mouse_position()
	var last_point = line.get_point_position(line.get_point_count() - 1)
	
	var target_direction = atan2(mouse_pos.y - last_point.y, 500.0)
	current_direction = lerp_angle(current_direction, target_direction, smooth_factor)
	
	var new_point = last_point + Vector2(
		cos(current_direction) * x_increment,
		sin(current_direction) * x_increment
	)
	
	var max_x = start_point.x + max_line_length
	if new_point.x > max_x:
		new_point.x = max_x
		new_point.y = last_point.y + sin(current_direction) * x_increment * 2.0
	
	line.add_point(new_point)
	move_points_left()
	light_smooth_line()
	
	# 更新光圈
	if is_pulsing:
		pulse_radius += pulse_speed * timer.wait_time
		if pulse_radius >= max_pulse_radius:
			is_pulsing = false
			pulse_radius = 0.0
		
		# 检测障碍物边缘
		detect_obstacle_edges(last_point)

func move_points_left():
	for i in range(line.get_point_count()):
		var point_pos = line.get_point_position(i)
		point_pos.x -= move_speed
		line.set_point_position(i, point_pos)
	
	while line.get_point_count() > 0 and line.get_point_position(0).x < start_point.x - 50:
		line.remove_point(0)

func light_smooth_line():
	var points_count = line.get_point_count()
	if points_count < 3:
		return
	
	for i in range(1, points_count - 1):
		var prev_point = line.get_point_position(i - 1)
		var current_point = line.get_point_position(i)
		var next_point = line.get_point_position(i + 1)
		
		var smoothed_point = current_point * 0.9 + (prev_point + next_point) * 0.05
		line.set_point_position(i, smoothed_point)

func _process(delta):
	if line.get_point_count() > 0:
		var mouse_pos = get_global_mouse_position()
		var last_point = line.get_point_position(line.get_point_count() - 1)
		var target_direction = atan2(mouse_pos.y - last_point.y, 500.0)
		
		current_direction = lerp_angle(current_direction, target_direction, smooth_factor * 10 * delta)
	
	# 更新边缘生命周期
	update_edge_lifetimes(delta)
	queue_redraw()

func _input(event):
	if event is InputEventMouseButton and event.pressed and event.button_index == MOUSE_BUTTON_LEFT:
		if line.get_point_count() > 0 and not is_pulsing:
			start_pulse()

func start_pulse():
	is_pulsing = true
	pulse_radius = 0.0

func detect_obstacle_edges(pulse_center: Vector2):
	var obstacles = get_tree().get_nodes_in_group("obstacle")
	
	for obstacle in obstacles:
		if obstacle is Area2D:
			var collision_polygon = obstacle.get_node("CollisionPolygon2D")
			if collision_polygon:
				# 获取多边形的全局坐标点
				var global_polygon = get_global_polygon_points(obstacle, collision_polygon)
				
				# 检测每条边与光圈的相交
				for i in range(global_polygon.size()):
					var p1 = global_polygon[i]
					var p2 = global_polygon[(i + 1) % global_polygon.size()]
					
					var intersections = get_circle_line_intersections(pulse_center, pulse_radius, p1, p2)
					
					# 存储相交的边
					if intersections.size() > 0:
						add_edge_segment(p1, p2, intersections)

func get_global_polygon_points(obstacle: Area2D, collision_polygon: CollisionPolygon2D) -> PackedVector2Array:
	var global_points = PackedVector2Array()
	
	# CollisionPolygon2D的polygon是局部坐标，需要转换到全局
	for point in collision_polygon.polygon:
		# 多边形点 + CollisionPolygon2D位置 + 障碍物位置
		var global_point = obstacle.global_position + collision_polygon.position + point
		global_points.append(global_point)
	
	return global_points

func get_circle_line_intersections(circle_center: Vector2, radius: float, line_start: Vector2, line_end: Vector2) -> PackedVector2Array:
	var intersections = PackedVector2Array()
	
	# 将线段转换为从circle_center出发的向量
	var d = line_end - line_start
	var f = line_start - circle_center
	
	var a = d.dot(d)
	var b = 2 * f.dot(d)
	var c = f.dot(f) - radius * radius
	
	var discriminant = b * b - 4 * a * c
	
	if discriminant >= 0:
		discriminant = sqrt(discriminant)
		var t1 = (-b - discriminant) / (2 * a)
		var t2 = (-b + discriminant) / (2 * a)
		
		if 0 <= t1 and t1 <= 1:
			intersections.append(line_start + d * t1)
		
		if 0 <= t2 and t2 <= 1 and abs(t1 - t2) > 0.001:
			intersections.append(line_start + d * t2)
	
	return intersections

func add_edge_segment(p1: Vector2, p2: Vector2, intersections: PackedVector2Array):
	# 如果边与光圈相交，存储这条边的信息
	var edge_data = {
		"points": [p1, p2],
		"lifetime": edge_lifetime
	}
	
	# 检查是否已经有相同的边
	for i in range(detected_edges.size()):
		var existing_edge = detected_edges[i]
		var existing_p1 = existing_edge["points"][0]
		var existing_p2 = existing_edge["points"][1]
		
		# 如果边相同（允许顺序颠倒）
		if (p1.distance_to(existing_p1) < 5.0 and p2.distance_to(existing_p2) < 5.0) or \
		   (p1.distance_to(existing_p2) < 5.0 and p2.distance_to(existing_p1) < 5.0):
			# 更新现有点的生命周期
			detected_edges[i]["lifetime"] = edge_lifetime
			return
	
	# 添加新边
	detected_edges.append(edge_data)

func update_edge_lifetimes(delta):
	var i = 0
	while i < detected_edges.size():
		detected_edges[i]["lifetime"] -= delta
		if detected_edges[i]["lifetime"] <= 0:
			detected_edges.remove_at(i)
		else:
			i += 1

func _draw():
	# 绘制正在发射的光圈
	if is_pulsing and line.get_point_count() > 0:
		var pulse_center = line.get_point_position(line.get_point_count() - 1)
		
		# 光圈主体（半透明）
		draw_circle(pulse_center, pulse_radius, Color(1, 1, 1, 0.1))
		
		# 光圈边缘（实线）
		draw_arc(pulse_center, pulse_radius, 0, TAU, 64, edge_color, 1.0)
	
	# 绘制检测到的障碍物边缘
	for edge in detected_edges:
		var alpha = edge["lifetime"] / edge_lifetime  # 淡出效果
		var color_with_alpha = Color(1, 1, 1, alpha)
		
		# 绘制边线
		var points = edge["points"]
		if points.size() >= 2:
			draw_line(points[0], points[1], color_with_alpha, 2.0, true)
			
			# 在边的两端绘制小圆点
			draw_circle(points[0], 3.0, color_with_alpha)
			draw_circle(points[1], 3.0, color_with_alpha)
